package Visitor;

import Arbori.Nod;
import FunctiiElementare.*;
import FunctiiTrigo.*;
import Operatori.*;

public class DerivareVisitor extends Visitor {
	protected String rezultat;
	protected ToStringVisitor tsv = new ToStringVisitor();

	public DerivareVisitor() {
		rezultat = "";
	}

	public DerivareVisitor(String s) {
		this.rezultat = s;
	}

	public String getRezultat() {
		return rezultat;
	}

	public String getS() {
		return rezultat;
	}

	public void setRezultat(String rezultat) {
		this.rezultat = rezultat;
	}

	public void visit(Cat c) {
		if (c.getFStang() != null && c.getFDrept() != null) {
			visit(c.getFStang());
			String f1D = this.rezultat;
			visit(c.getFDrept());
			String f2D = this.rezultat;
			c.getFStang().acceptVisitor(tsv);
			String f1 = tsv.getS();
			c.getFDrept().acceptVisitor(tsv);
			String f2 = tsv.getS();
			this.rezultat = Cat.concatTermens(
					Minus.concatTermens(Produs.concatTermens(f1D, f2),
							Produs.concatTermens(f1, f2D)),
					Putere.concatTermens(f2, "2"));
		}
	}

	public void visit(Constanta ct) {
		this.rezultat = "0";
	}

	public void visit(Cos s) {
		if (s.getFStang() != null) {
			visit(s.getFStang());
			String fsd = this.rezultat;
			s.getFStang().acceptVisitor(tsv);
			String fs = tsv.getS();
			this.rezultat = Produs.concatTermens(
					Produs.concatTermens("-1", Sin.concatTermens(fs)), fsd);
		}
	}

	public void visit(Minus m) {
		if (m.getFStang() != null && m.getFDrept() != null) {
			visit(m.getFStang());
			String s1 = this.rezultat;
			visit(m.getFDrept());
			String s2 = this.rezultat;
			rezultat = m.concatTermeni(s1, s2);
		}
	}

	public void visit(Necunoscuta n) {
		this.rezultat = "1";
	}

	public void visit(Nod n) {
		if (n.toString().contains("Plus"))
			visit((Plus) n);
		else if (n.toString().contains("Constanta"))
			visit((Constanta) n);
		else if (n.toString().contains("Necunoscuta"))
			visit((Necunoscuta) n);
		else if (n.toString().contains("Minus"))
			visit((Minus) n);
		else if (n.toString().contains("Cat"))
			visit((Cat) n);
		else if (n.toString().contains("Produs"))
			visit((Produs) n);
		else if (n.toString().contains("Putere"))
			visit((Putere) n);
		else if (n.toString().contains("Cos"))
			visit((Cos) n);
		else if (n.toString().contains("Sin"))
			visit((Sin) n);
		else if (n.toString().contains("Tg"))
			visit((Tg) n);
		else if (n.toString().contains("Ctg"))
			visit((Ctg) n);
		else if (n.toString().contains("Sqrt"))
			visit((Sqrt) n);
		else if (n.toString().contains("Ln"))
			visit((Ln) n);
		else if (n.toString().contains("Log"))
			visit((Log) n);
		else if (n.toString().contains("Exp"))
			visit((Exp) n);
	}

	public void visit(Plus p) {
		if (p.getFStang() != null && p.getFDrept() != null) {
			visit(p.getFStang());
			String s1 = this.rezultat;
			visit(p.getFDrept());
			String s2 = this.rezultat;
			rezultat = p.concatTermeni(s1, s2);
		}
	}

	public void visit(Produs p) {
		if (p.getFStang() != null && p.getFDrept() != null) {
			visit(p.getFStang());
			String f1D = this.rezultat;
			visit(p.getFDrept());
			String f2D = this.rezultat;
			p.getFStang().acceptVisitor(tsv);
			String f1 = tsv.getS();
			p.getFDrept().acceptVisitor(tsv);
			String f2 = tsv.getS();
			this.rezultat = Plus.concatTermens(Produs.concatTermens(f1D, f2),
					Produs.concatTermens(f2D, f1));
		}
	}

	public void visit(Sin s) {
		if (s.getFStang() != null) {
			visit(s.getFStang());
			String fsd = this.rezultat;
			s.getFStang().acceptVisitor(tsv);
			String fs = tsv.getS();
			this.rezultat = Produs.concatTermens(Cos.concatTermens(fs), fsd);
		}
	}
}
